﻿using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;

using System.Collections.Generic;

namespace FlockTest
{
    public partial class Page : Canvas
    {
        Dictionary<Ellipse, FlockElement> flockui = new Dictionary<Ellipse, FlockElement>();
        private Ellipse flockpoint;
        Flock flock;

        Vector farpoint = new Vector(Global.BOUNDING_X, 0, Global.BOUNDING_Z);
        float maxFarPoint = 0;

        public void Page_Loaded(object o, EventArgs e)
        {
            // Required to initialize variables
            InitializeComponent();
            initFlock();
            InitTick();

            drawAxis();
        }

        public void initFlock()
        {
            flock = new Flock(50);

            foreach (FlockElement fe in flock.flock)
            {
                Ellipse el = new Ellipse();
                el.Height = 5;
                el.Width = 5;

                this.Children.Add(el);
                flockui.Add(el, fe);
            }


            // Display Flock Point
            flockpoint = new Ellipse();
            flockpoint.Height = 5;
            flockpoint.Width = 5;
            flockpoint.Fill = new SolidColorBrush(Colors.Yellow);

            flockpoint.SetValue(Canvas.LeftProperty, Flock.FlockToPoint.X);
            flockpoint.SetValue(Canvas.TopProperty, Flock.FlockToPoint.Y);
            this.Children.Add(flockpoint);

            maxFarPoint = Vector.Magnitude(farpoint - new Vector(0, 0, 0));
        }



        // Start Tick
        private void InitTick()
        {
            Storyboard timerTimeline = new Storyboard();
            timerTimeline.Duration = new Duration( new TimeSpan(0,0,0,0,50) );
            this.Resources.Add(timerTimeline);
            timerTimeline.Begin();
            timerTimeline.Completed += new EventHandler(Tick);


        }


        private void Tick(Object sender, EventArgs e)
        {
            foreach (Ellipse el in flockui.Keys)
            {
                float distFromFarPoint = maxFarPoint - Vector.Magnitude(farpoint - flockui[el].Coordinates);
                float percfromFP = distFromFarPoint / maxFarPoint;

                el.SetValue(Canvas.LeftProperty,
                    FlockMath.D3_ISOMetric_MEN2536_C_M(flockui[el].Coordinates).X
                    );
                el.SetValue(Canvas.TopProperty,
                    FlockMath.D3_ISOMetric_MEN2536_C_M(flockui[el].Coordinates).Y);

                el.Width = 10 * percfromFP;
                el.Height = 10 * percfromFP;

                // Set Color
                byte colorByte = Convert.ToByte((1-percfromFP) * 100F);
                if (flockui[el].IsLeader) el.Fill = new SolidColorBrush(Color.FromRgb(255, colorByte, colorByte));
                else el.Fill = new SolidColorBrush(Color.FromRgb(colorByte, colorByte, 255));

           }

            flockpoint.SetValue(Canvas.LeftProperty, 
                FlockMath.D3_ISOMetric_MEN2536_C_M(Flock.FlockToPoint).X);
            flockpoint.SetValue(Canvas.TopProperty, 
                FlockMath.D3_ISOMetric_MEN2536_C_M(Flock.FlockToPoint).Y);

            ((Storyboard)sender).Begin(); 
        }

        private void drawAxis()
        {
            // x,y,z    x,y,z
            // 0,0,0 to 1,0,0
            // 0,0,0 to 0,1,0
            // 0,0,0 to 0,0,1

            Vector xAxis = new Vector(Global.BOUNDING_X, 0, 0);
            Vector yAxis = new Vector(0, Global.BOUNDING_Y, 0);
            Vector zAxis = new Vector(0, 0, Global.BOUNDING_Z);
            Vector root = new Vector(0, 0, 0);

            Vector yxMax = new Vector(Global.BOUNDING_X, Global.BOUNDING_Y, 0);
            Vector xzMax = new Vector(Global.BOUNDING_X , 0, Global.BOUNDING_Z );
            Vector yzMax = new Vector(0, Global.BOUNDING_Y , Global.BOUNDING_Z );
            Vector xyzMax = new Vector(Global.BOUNDING_X , Global.BOUNDING_Y , Global.BOUNDING_Z);

            Vector xiso = FlockMath.D3_ISOMetric_MEN2536_C_M(xAxis);
            Vector yiso = FlockMath.D3_ISOMetric_MEN2536_C_M(yAxis);
            Vector ziso = FlockMath.D3_ISOMetric_MEN2536_C_M(zAxis);
            Vector rootiso = FlockMath.D3_ISOMetric_MEN2536_C_M(root);

            Vector yxiso = FlockMath.D3_ISOMetric_MEN2536_C_M(yxMax);
            Vector xziso = FlockMath.D3_ISOMetric_MEN2536_C_M(xzMax);
            Vector yziso = FlockMath.D3_ISOMetric_MEN2536_C_M(yzMax);
            Vector xyziso = FlockMath.D3_ISOMetric_MEN2536_C_M(xyzMax);


            Line x = new Line(); x.StrokeThickness = 3;
            x.X1 = rootiso.X; x.Y1 = rootiso.Y; x.X2 = xiso.X; x.Y2 = xiso.Y;
            x.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(x);

            Line y = new Line(); y.StrokeThickness = 3;
            y.X1 = rootiso.X; y.Y1 = rootiso.Y; y.X2 = yiso.X; y.Y2 = yiso.Y;
            y.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(y);

            Line z = new Line(); z.StrokeThickness = 3;
            z.X1 = rootiso.X; z.Y1 = rootiso.Y; z.X2 = ziso.X; z.Y2 = ziso.Y;
            z.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(z);

            Line yx = new Line(); yx.StrokeThickness = 3;
            yx.X1 = yiso.X; yx.Y1 = yiso.Y; yx.X2 = yxiso.X; yx.Y2 = yxiso.Y;
            yx.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(yx);

            Line xy = new Line(); xy.StrokeThickness = 3;
            xy.X1 = xiso.X; xy.Y1 = xiso.Y; xy.X2 = yxiso.X; xy.Y2 = yxiso.Y;
            xy.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(xy);

            Line xz = new Line(); xz.StrokeThickness = 3;
            xz.X1 = xiso.X; xz.Y1 = xiso.Y; xz.X2 = xziso.X; xz.Y2 = xziso.Y;
            xz.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(xz);

            Line zx = new Line(); zx.StrokeThickness = 3;
            zx.X1 = ziso.X; zx.Y1 = ziso.Y; zx.X2 = xziso.X; zx.Y2 = xziso.Y;
            zx.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(zx);

            Line yz = new Line(); yz.StrokeThickness = 3;
            yz.X1 = yiso.X; yz.Y1 = yiso.Y; yz.X2 = yziso.X; yz.Y2 = yziso.Y;
            yz.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(yz);

            Line zy = new Line(); zy.StrokeThickness = 3;
            zy.X1 = ziso.X; zy.Y1 = ziso.Y; zy.X2 = yziso.X; zy.Y2 = yziso.Y;
            zy.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(zy);

            Line yx_xyz = new Line(); yx_xyz.StrokeThickness = 3;
            yx_xyz.X1 = yxiso.X; yx_xyz.Y1 = yxiso.Y; yx_xyz.X2 = xyziso.X; yx_xyz.Y2 = xyziso.Y;
            yx_xyz.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(yx_xyz);

            Line xz_xyz = new Line(); xz_xyz.StrokeThickness = 3;
            xz_xyz.X1 = xziso.X; xz_xyz.Y1 = xziso.Y; xz_xyz.X2 = xyziso.X; xz_xyz.Y2 = xyziso.Y;
            xz_xyz.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(xz_xyz);

            Line yz_xyz = new Line(); yz_xyz.StrokeThickness = 3;
            yz_xyz.X1 = yziso.X; yz_xyz.Y1 = yziso.Y; yz_xyz.X2 = xyziso.X; yz_xyz.Y2 = xyziso.Y;
            yz_xyz.Stroke = new SolidColorBrush(Colors.Green);
            this.Children.Add(yz_xyz);
        }
    }
}
